<template>
	<view>
		<!-- #ifndef MP -->
		<canvas :canvas-id="canvasId" :id="canvasId" :style="{ width: `${width}px`, height: `${height}px`}" class="cCanvas"></canvas>
		<!-- #endif -->
	</view>
</template>

<script setup>
	/**
	 * c-canvas 绘制海报组件
	 * @property {String} canvasId 画布id
	 * @property {Boolean} isAuto 是否自动绘制
	 * @property {Number} width 画布宽度
	 * @property {Number} height 画布高度
	 * @property {Array} drawData 绘制的数据  [{type: 'image',x: 0,y: 0,value: 'https://vkceyugu.cdn.bspapp.com/VKCEYUGU-3e51af12-a055-4f58-b1ad-7710dd05bfc4/17d972b6-6c4e-4cab-a8c0-e9ee832ecc63.jpg',width:375,height:375},
		{type: 'text',x: 10,y: 20,value: '这是一段文字',color: '#F1D7A4',textAlign: 'center',font:'normal 400 12px sans-serif',lineHeight:20,lineMaxWidth:200,lineNum:1},]
	 * @event {Function()} drawSuccess 绘制成功 返回导出的图片路径
	 * */
	import {nextTick,getCurrentInstance} from 'vue'
	const props = defineProps({
		canvasId:{
			type:String,
			default:'myCanvas'
		},
		isAuto:{
			type:Boolean,
			default:true
		},
		//画布宽度
		width: {
			type: Number,
			default: 375
		},
		//画布高度
		height: {
			type: Number,
			default: 375
		},
		drawData: {
			type: Array,
			default: () => {
				return []
			}
		}
	})
	const emits= defineEmits(['drawSuccess'])
	let ctx=null,thumb = null
	const drawText = (item) => {
			if(item.font)ctx.font=item.font;
			if(item.color)ctx.setFillStyle(item.color)
			if(item.textAlign&&item.x&&item.y)ctx.setTextAlign(item.textAlign)
			// if(item.value)ctx.fillText(item.value,item.x||0,item.y||0)
			if(item.value)textPrewrap(ctx,item.value,item.x||0,item.y||0,item.lineHeight||20,item.lineMaxWidth||200,item.lineNum||1)
			
	}
	const drawImage=async (item)=>{
		let Img =item.value
		// #ifndef H5
			if(checkUrl(Img)){
				let res = await uni.downloadFile({url:item.value})
				Img = res.tempFilePath
			}
		// #endif
		if(item.radius){
			drawRoundRect(item.radius,item.x||0,item.y||0,item.width,item.height,Img)
		}else{
			ctx.drawImage(Img,item.x||0,item.y||0,item.width,item.height)
		}
	}
	
	/*
	 *  参数说明
	 *  ctx Canvas实例
	 *  img 图片地址
	 *   x  x轴坐标
	 *   y  y轴坐标
	 *   w  宽度
	 *   h  高度
	 *   r  弧度大小
	 */
   const drawRoundRect=(r, x, y, w, h, img)=>{
	  ctx.save();
	  if (w < 2 * r) r = w / 2;
	  if (h < 2 * r) r = h / 2;
	  ctx.beginPath();
	  ctx.moveTo(x + r, y);
	  ctx.arcTo(x + w, y, x + w, y + h, r);
	  ctx.arcTo(x + w, y + h, x, y + h, r);
	  ctx.arcTo(x, y + h, x, y, r);
	  ctx.arcTo(x, y, x + w, y, r);
	  ctx.closePath();
	  ctx.clip();
	  ctx.drawImage(img, x, y, w, h);
	  ctx.restore(); // 返回上一状态
	}
	const draw =async () => {
		if(thumb){
			emits('drawSuccess',thumb)
			return
		}
		ctx = uni.createCanvasContext(props.canvasId,getCurrentInstance())
		for(let item of props.drawData){
			if (item.type == 'text') {
				drawText(item)
			}else if(item.type == 'image'){
				await drawImage(item)
			}
		}
		
		ctx.draw(false, () => {
			console.log('绘制完成');
			setTimeout(()=>{
				uni.canvasToTempFilePath({
					  canvasId: props.canvasId,
					  quality:1,
					  success:(ret)=>{
						// 在H5平台下，tempFilePath 为 base64
						thumb = ret.tempFilePath
						emits('drawSuccess',thumb)
					  },
					  fail: (err) => {
						console.log(err);
					  }
				})
			},80)
			
		})
		
	}
	nextTick(()=>{
		if(props.isAuto)draw()
	})
	defineExpose({draw})
	const checkUrl=(url)=>{
		return /(http|https):\/\/([\w.]+\/?)\S*/.test(url)
	}
	const textPrewrap=(ctx, content, drawX, drawY, lineHeight, lineMaxWidth, lineNum)=> {
		let drawTxt = ''; // 当前绘制的内容
		let drawLine = 1; // 第几行开始绘制
		let drawIndex = 0; // 当前绘制内容的索引

    // 判断内容是否可以一行绘制完毕
    if(ctx.measureText(content).width <= lineMaxWidth) {
        ctx.fillText(content, drawX, drawY);
    } else {
        for (let i = 0; i <= content.length; i++) {
            drawTxt += content[i];
                if (drawLine === lineNum&&i==content.length) {
					if (ctx.measureText(drawTxt).width > lineMaxWidth) {
						// 最后一行添加省略号
						ctx.fillText(content.substring(drawIndex, i) + '...', drawX, drawY);
					}else{
						ctx.fillText(content.substring(drawIndex, i), drawX, drawY);
					}
                } else {
					if (ctx.measureText(drawTxt).width > lineMaxWidth) {
						// 不是最后一行的情况
						ctx.fillText(content.substring(drawIndex, i + 1), drawX, drawY);
						drawIndex = i + 1;  // 记录当前行最后一个字符串的下一个idnex，用于绘制下行第一个字
						drawLine += 1;  // 行数+1
						drawY += lineHeight; // 绘制内容的y坐标对应增加行高
						drawTxt = ''; // 重置绘制的内容
					}
                }
        }
    }
}
</script>

<style lang="scss">
.cCanvas{
	position: fixed;
	top: -10000px;
}
</style>
